package com.market.domain;

import java.util.ArrayList;
import java.util.List;
import java.util.Locale;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.ManyToMany;
import javax.persistence.Table;
import javax.persistence.Transient;

import com.market.domain.Product.SOURCE;

@Entity
@Table(name = "producttheme")
public class ProductTheme extends BaseObject {

	/**
	 * 
	 */
	private static final long serialVersionUID = -8380190655606943707L;

	@Override
	public boolean equalsId(Object o) {
		if (o instanceof ProductTheme
				&& ((ProductTheme) o).getId().equals(this.id)) {
			return true;
		}
		return false;
	}

	public String getNameLabel() {
		return super.getLabel("Name", super.getLocale());
	}

	public String getDescriptionLabel() {
		return super.getLabel("Description", super.getLocale());
	}

	@Transient
	private List<Product> filteredProducts;

	public List<Product> getFilteredProducts() {
		return filteredProducts;
	}

	public void setFilteredProducts(List<Product> filteredProducts) {
		this.filteredProducts = filteredProducts;
	}

	@Transient
	private List<ProductPrice> productPrices = new ArrayList<ProductPrice>();

	public List<ProductPrice> getProductPrices() {
		return productPrices;
	}

	public void setProductPrices(List<ProductPrice> productPrices) {
		this.productPrices = productPrices;
	}

	/**
	 * This method import productPices from specific list, this list will be
	 * filtered by the productList of this productTheme.
	 * 
	 * @param productPrices
	 */
	public void importProductPrices(List<ProductPrice> productPrices) {
		this.productPrices.clear();
		for (Product product : this.products) {
			for (ProductPrice price : productPrices) {
				if (product.equalsId(price.getProduct())) {
					this.productPrices.add(price);
					break;
				}
			}
		}

	}

	/**
	 * This method import all products on sale from specific productPrices list.
	 * A typical use is import from productPrices list of specific list.
	 * 
	 * This method also set this theme's name property, because "onSale" theme
	 * is very special.
	 * 
	 * @param productPrices
	 */
	public void importOnSaleProductPrices(List<ProductPrice> productPrices) {
		this.productPrices.clear();
		for (ProductPrice productPrice : productPrices) {
			if (productPrice.getIsOnSpecial()) {
				this.productPrices.add(productPrice);
			}
		}
		this.name = super.getMessage("onSale", Locale.ENGLISH);
		this.chineseName = super.getMessage("onSale", Locale.CHINESE);
		this.frenchName = super.getMessage("onSale", Locale.FRENCH);
	}

	/**
	 * This method import all products from our farm from specific productPrices
	 * list. A typical use is import from productPrices list of specific list.
	 * 
	 * This method also set this theme's name property, because "fromOurFarm"
	 * theme is very special.
	 * 
	 * @param productPrices
	 */
	public void importFromOurFarmProductPrices(List<ProductPrice> productPrices) {
		this.productPrices.clear();
		for (ProductPrice productPrice : productPrices) {
			if (productPrice.getProduct().getSource() == SOURCE.OUR_FARM) {
				this.productPrices.add(productPrice);
			}
		}
		this.name = super.getMessage("fromOurFarm", Locale.ENGLISH);
		this.chineseName = super.getMessage("fromOurFarm", Locale.CHINESE);
		this.frenchName = super.getMessage("fromOurFarm", Locale.FRENCH);
	}

	/**
	 * This method import all products that is directly from local farm from
	 * specific productPrices list. A typical use is import from productPrices
	 * list of specific list.
	 * 
	 * This method also set this theme's name property, because "farmDirect"
	 * theme is very special.
	 * 
	 * @param productPrices
	 */
	public void importFarmDirectProductPrices(List<ProductPrice> productPrices) {
		this.productPrices.clear();
		for (ProductPrice productPrice : productPrices) {
			if (productPrice.getProduct().getSource() == SOURCE.FARM_DIRECT
					|| productPrice.getProduct().getSource() == SOURCE.PRODUCER_DIRECT) {
				this.productPrices.add(productPrice);
			}
		}
		this.name = super.getMessage("farmDirect", Locale.ENGLISH);
		this.chineseName = super.getMessage("farmDirect", Locale.CHINESE);
		this.frenchName = super.getMessage("farmDirect", Locale.FRENCH);
	}

	@Id
	@GeneratedValue(strategy = GenerationType.AUTO)
	private Long id = 0L;
	@Column(length = 100)
	private String name;
	@Column(length = 100)
	private String chineseName;
	@Column(length = 100)
	private String frenchName;
	@Column(length = 1000)
	private String description;
	@Column(length = 1000)
	private String chineseDescription;
	@Column(length = 1000)
	private String frenchDescription;
	@Column(columnDefinition = "bit(1) default 0")
	private Boolean isActive = Boolean.FALSE;
	@Column(columnDefinition = "int Default 50")
	private Integer recommendIndex = 50;
	@ManyToMany(cascade = javax.persistence.CascadeType.ALL, fetch = FetchType.LAZY)
	private List<Product> products = new ArrayList<Product>();

	public Long getId() {
		return id;
	}

	public void setId(Long id) {
		this.id = id;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public String getChineseName() {
		return chineseName;
	}

	public void setChineseName(String chineseName) {
		this.chineseName = chineseName;
	}

	public String getFrenchName() {
		return frenchName;
	}

	public void setFrenchName(String frenchName) {
		this.frenchName = frenchName;
	}

	public String getDescription() {
		return description;
	}

	public void setDescription(String description) {
		this.description = description;
	}

	public String getChineseDescription() {
		return chineseDescription;
	}

	public void setChineseDescription(String chineseDescription) {
		this.chineseDescription = chineseDescription;
	}

	public String getFrenchDescription() {
		return frenchDescription;
	}

	public void setFrenchDescription(String frenchDescription) {
		this.frenchDescription = frenchDescription;
	}

	public Boolean getIsActive() {
		return isActive;
	}

	public void setIsActive(Boolean isActive) {
		this.isActive = isActive;
	}

	public Integer getRecommendIndex() {
		return recommendIndex;
	}

	public void setRecommendIndex(Integer recommendIndex) {
		this.recommendIndex = recommendIndex;
	}

	public List<Product> getProducts() {
		return products;
	}

	public void setProducts(List<Product> products) {
		this.products = products;
	}

	@Override
	public String toString() {
		return "ProductTheme [id=" + id + ", name=" + name + ", chineseName="
				+ chineseName + ", frenchName=" + frenchName + ", description="
				+ description + ", chineseDescription=" + chineseDescription
				+ ", frenchDescription=" + frenchDescription + "]";
	}

	@Override
	public int hashCode() {
		final int prime = 31;
		int result = 1;
		result = prime
				* result
				+ ((chineseDescription == null) ? 0 : chineseDescription
						.hashCode());
		result = prime * result
				+ ((chineseName == null) ? 0 : chineseName.hashCode());
		result = prime * result
				+ ((description == null) ? 0 : description.hashCode());
		result = prime
				* result
				+ ((frenchDescription == null) ? 0 : frenchDescription
						.hashCode());
		result = prime * result
				+ ((frenchName == null) ? 0 : frenchName.hashCode());
		result = prime * result + ((name == null) ? 0 : name.hashCode());
		return result;
	}

	@Override
	public boolean equals(Object obj) {
		if (this == obj)
			return true;
		if (obj == null)
			return false;
		if (getClass() != obj.getClass())
			return false;
		ProductTheme other = (ProductTheme) obj;
		if (chineseDescription == null) {
			if (other.chineseDescription != null)
				return false;
		} else if (!chineseDescription.equals(other.chineseDescription))
			return false;
		if (chineseName == null) {
			if (other.chineseName != null)
				return false;
		} else if (!chineseName.equals(other.chineseName))
			return false;
		if (description == null) {
			if (other.description != null)
				return false;
		} else if (!description.equals(other.description))
			return false;
		if (frenchDescription == null) {
			if (other.frenchDescription != null)
				return false;
		} else if (!frenchDescription.equals(other.frenchDescription))
			return false;
		if (frenchName == null) {
			if (other.frenchName != null)
				return false;
		} else if (!frenchName.equals(other.frenchName))
			return false;
		if (name == null) {
			if (other.name != null)
				return false;
		} else if (!name.equals(other.name))
			return false;
		return true;
	}

}
